package com.task;

import java.util.concurrent.TimeUnit;
import java.util.concurrent.atomic.AtomicReference;

/**
 * @author: cxt
 * @time: 2022/11/27
 * 自旋锁实现，利用 AtomicReference
 */
public class SpinDemo {
    /**
     * 定义AtomicReference并且初始值为
     */
    // private static AtomicReference<SysUser> debitCardRef = new AtomicReference<>(new SysUser(初始值));
    // 初始值为null，相当于内存值为null
    AtomicReference<Thread> atomicReference = new AtomicReference<>();

    public static void main(String[] args) {
        long l = System.currentTimeMillis();
        SpinDemo demo = new SpinDemo();
        new Thread(() -> {
            demo.lock();
            demo.business();
            demo.unLock();
        }, "线程A").start();

        // 确保A先开始
        try {
            TimeUnit.MILLISECONDS.sleep(10);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }

        new Thread(() -> {
            demo.lock();
            demo.business();
            demo.unLock();
        }, "线程B").start();
        System.out.println("耗时" + (l - (System.currentTimeMillis())));
    }

    public void lock() {
        Thread thread = Thread.currentThread();
        String threadName = Thread.currentThread().getName();
        System.out.println(threadName + "线程已加入");
        while (!atomicReference.compareAndSet(null, thread)) {
            System.out.println(Thread.currentThread().getName() + "自旋中");
        }
        System.out.println(threadName + "线程已获得锁");
    }

    public void unLock() {
        Thread thread = Thread.currentThread();
        atomicReference.compareAndSet(thread, null);
        System.out.println(Thread.currentThread().getName() + "线程已退出");
    }

    public void business() {
        System.out.println(Thread.currentThread().getName() + "开始执行业务");
        try {
            TimeUnit.MILLISECONDS.sleep(100);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        System.out.println(Thread.currentThread().getName() + "执行完成");
    }
}
